package chen.web.forum;

import java.util.Date;
import java.util.List;
import java.util.Timer;
import java.util.TimerTask;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import chen.web.SystemProperties;
import chen.web.util.DateInt;

/**
 * 维护"今日发帖""昨日发帖"等数据。每次启动后和每天定时维护数据
 * @author chen
 *
 */
public class PostCountResetTask extends TimerTask{
	
	private static Log log = LogFactory.getLog(PostCountResetTask.class);

	private static final String PostCountResetDatePropertyName = "today_yesterday_post_count_reset_date";
	
	private CategoryManager cm;
	public PostCountResetTask(CategoryManager cm){
		this.cm = cm;
		resetTodayPostCount(cm.getRootCategory());
	}
	
	private Timer timer = new Timer();
	public void start(){
		timer.schedule(this, CategoryDynamicInfo.tomorrow(), 24*3600*1000);
	}
	
	public void stop(){
		timer.cancel();
	}
	
	/**
	 * 由于"今日发帖""昨日发帖"等数据是有状态的，需要每天定时维护，当服务器出现意外没有维护，则数据会不正确。
	 * 所以每次加载栏目信息后需要调用此方法，能保证这些数据的准确性
	 * @see PostCountResetTask
	 * @param root
	 */
	private static void resetTodayPostCount(Category root){
		Date resetDate = lastResetDate();
		//resetDate为null表示此任务是第一次启动
		if(resetDate == null){
			updateLastResetDate();
			log.info("初始化属性值：" + PostCountResetDatePropertyName);
			return;
		}
		
		if(_resetTodayPostCount(root, new Flag(), resetDate)){
			updateLastResetDate();
			log.warn("由于今天没有更新‘今日发帖量’‘昨日发帖量’等数据，重设数据");
		}
	}
	

	private static class Flag{
		private boolean flag = false;
	}
	/**
	 * 递归reset, 若有reset行为返回true,否则返回false
	 * @param root
	 * @param flag
	 * @return
	 */
	private static boolean _resetTodayPostCount(Category root, Flag flag, Date resetDate){
		CategoryDynamicInfo info = root.getDynamicInfo();
		Date today = CategoryDynamicInfo.today();
		Date yesterday = CategoryDynamicInfo.yesterday();
		
		//两天没有reset
		if(resetDate.compareTo(yesterday) < 0){ 
			info.setYesterdayPostCount(0);
			info.setTodayPostCount(0);
			CategoryDynamicInfoManager.updateDynamicInfo(root);
			flag.flag = true;
		}else if(resetDate.compareTo(today) < 0){ //一天没有reset
			info.setYesterdayPostCount(info.getTodayPostCount());
			info.setTodayPostCount(0);
			CategoryDynamicInfoManager.updateDynamicInfo(root);
			flag.flag = true;
		}
		List<Category> children = root.getChildren();
		if(children != null && children.size()>0){
			for(Category child : children){
				_resetTodayPostCount(child, flag, resetDate);
			}
		}
		return flag.flag;
	}
	
	@Override
	public void run() {
		// TODO Auto-generated method stub
		Category root = cm.getRootCategory();
		resetYesterdayPost(root);
		resetTodayPost(root);
		persist(root);
		updateLastResetDate();
		log.info("更新‘今日发帖量’‘昨日发帖量’等数据");
	}
	
	private static Date lastResetDate(){
		String value = SystemProperties.getProperty(PostCountResetDatePropertyName);
		if(value == null) return null;
		return DateInt.transform(Integer.parseInt(value));
	}
	
	private static void updateLastResetDate(){
		SystemProperties.setProperty(PostCountResetDatePropertyName, String.valueOf(DateInt.transform(new Date())));
	}
	
	private void persist(Category cat){
		CategoryDynamicInfoManager.updateDynamicInfo(cat);
		List<Category> children = cat.getChildren();
		if(children != null && children.size()>0){
			for(Category child : children){
				persist(child);
			}
		}
	}
	
	private void resetYesterdayPost(Category cat){
		CategoryDynamicInfo info = cat.getDynamicInfo();
		info.setYesterdayPostCount(info.getTodayPostCount());
		List<Category> children = cat.getChildren();
		if(children != null && children.size()>0){
			for(Category child : children){
				resetYesterdayPost(child);
			}
		}
	}
	
	private void resetTodayPost(Category cat){
		CategoryDynamicInfo info = cat.getDynamicInfo();
		info.setTodayPostCount(0);
		List<Category> children = cat.getChildren();
		if(children != null && children.size()>0){
			for(Category child : children){
				resetTodayPost(child);
			}
		}
	}
	
}
